package com.jiandan.business.util.selfservice;

import java.util.ArrayList;
import java.util.List;

import net.sourceforge.pinyin4j.PinyinHelper;
import net.sourceforge.pinyin4j.format.HanyuPinyinCaseType;
import net.sourceforge.pinyin4j.format.HanyuPinyinOutputFormat;
import net.sourceforge.pinyin4j.format.HanyuPinyinToneType;
import net.sourceforge.pinyin4j.format.exception.BadHanyuPinyinOutputFormatCombination;

public class PinyinUtils {
	private static PinyinUtils instance = new PinyinUtils();
	private HanyuPinyinOutputFormat defaultFormat;

	private PinyinUtils() {
		super();
		defaultFormat = new HanyuPinyinOutputFormat();
		defaultFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);
		defaultFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);
	}

	public static PinyinUtils getInstance() {
		return instance;
	}

	/***/
	public String getPinyin(String chn) {
		// 重当参 ->
		// ,zhongdangcen,zhongdangcan,chongdangcen,chongdangshen,zhongdangshen,chongdangcan
		StringBuffer pinyin = new StringBuffer("");
		char[] nameChar = chn.toCharArray();
		List<String[]> pinyinList = new ArrayList<String[]>();
		List<String[]> pinyinAbbList = new ArrayList<String[]>();
		for (int i = 0; i < nameChar.length; i++) {
			if (Character.toString(nameChar[i]).matches("[\\u4E00-\\u9FA5]+")) {
				try {
					String[] multPinyin = PinyinHelper
							.toHanyuPinyinStringArray(nameChar[i],
									defaultFormat);
					multPinyin = getDistinct(multPinyin);
					String[] pinyinAbb = getPinyinAbb(multPinyin);
					pinyinAbb = getDistinct(pinyinAbb);
					pinyinList.add(multPinyin);
					pinyinAbbList.add(pinyinAbb);
				} catch (BadHanyuPinyinOutputFormatCombination e) {
					e.printStackTrace();
				}
			} else {
				pinyinList.add(new String[] { String.valueOf(nameChar[i]) });
				pinyinAbbList.add(new String[] { String.valueOf(nameChar[i]) });
			}
		}
		String[] allPinyinCombination = appendPinyin(pinyinList, 0);
		for (int i = 0; i < allPinyinCombination.length; i++) {
			pinyin.append(",").append(allPinyinCombination[i]);
		}
		String[] allPinyinAbbCombination = appendPinyin(pinyinAbbList, 0);
		for (int i = 0; i < allPinyinAbbCombination.length; i++) {
			pinyin.append(",").append(allPinyinAbbCombination[i]);
		}
		return pinyin.toString();
	}

	private String[] getDistinct(String[] multPinyin) {
		List<String> temp = new ArrayList<String>();
		for (int i = 0; i < multPinyin.length; i++) {
			if (!temp.contains(multPinyin[i])) {
				temp.add(multPinyin[i]);
			}
		}
		return temp.toArray(new String[temp.size()]);
	}

	private String[] getPinyinAbb(String[] multPinyin) {
		String[] pinyinAbb = new String[multPinyin.length];
		for (int i = 0; i < multPinyin.length; i++) {
			pinyinAbb[i] = multPinyin[i].substring(0, 1);
		}
		return pinyinAbb;
	}

	private String[] appendPinyin(List<String[]> pinyinList, int level) {
		// last level
		if (level >= pinyinList.size() - 1) {
			return pinyinList.get(level);
		} else {
			String[] thisLv = pinyinList.get(level);
			String[] deepLv = appendPinyin(pinyinList, level + 1);
			String[] temps = new String[thisLv.length * deepLv.length];
			for (int i = 0; i < thisLv.length; i++) {
				String thisStr = thisLv[i];
				for (int j = 0; j < deepLv.length; j++) {
					String deepStr = deepLv[j];
					temps[i * deepLv.length + j] = thisStr + deepStr;
				}
			}
			return temps;
		}
	}

}